//
//  Utils.hpp
//  myhttpserver
//
//  Created by tgy on 2018/3/19.
//  Copyright © 2018年 tgy. All rights reserved.
//

#ifndef Utils_hpp
#define Utils_hpp

#include <stdio.h>
#include <string>
#include <vector>
#include <iostream>
#include <unistd.h>
#include <fcntl.h>

typedef unsigned char BYTE;


class Utils {
public:
      static  void splitString(const std::string &s,std::vector<std::string> & v, const std::string &c){
    
            std::string::size_type pos1, pos2;
            pos2 = s.find(c);
            pos1 = 0;
            while(std::string::npos != pos2)
            {
                v.push_back(s.substr(pos1, pos2-pos1));
    
                pos1 = pos2 + c.size();
                pos2 = s.find(c, pos1);
            }
            if(pos1 != s.length())
                v.push_back(s.substr(pos1));
    
        }
    static void trimString(std::string &str){
        
        
        if (str.empty())
        {
            return;
        }
        
        str.erase(0,str.find_first_not_of(" "));
        str.erase(str.find_last_not_of(" ") + 1);
    }
    
    static bool canSendFileName(const std::string fileName){
        
        if (fileName == "." || fileName == ".." || fileName == ".DS_Store") {
            
            return false;
        }
        
        return true;
    }
    
    static bool  setNoBlock(int fd){
        
        int bf = fcntl(fd, F_GETFL,0);
        if (bf < 0) {
            
            perror("fcntl error");
            return false;
        }
        bf |= O_NONBLOCK;
        bf = fcntl(fd, F_SETFL,bf);
    
        if (bf < 0) {
            
            perror("fcntl error");
            return false;
        }
        
        return true;
    }
    
    

    
    static BYTE toHex(const BYTE &x)
    {
        return x > 9 ? x -10 + 'A': x + '0';
    }
    
    static BYTE fromHex(const BYTE &x)
    {
        return isdigit(x) ? x-'0' : x-'A'+10;
    }
    
    static std::string URLEncode(const std::string &sIn)
    {
        std::string sOut;
        for( size_t ix = 0; ix < sIn.size(); ix++ )
        {
            BYTE buf[4];
            memset( buf, 0, 4 );
            if( isalnum( (BYTE)sIn[ix] ) )
            {
                buf[0] = sIn[ix];
            }
            //else if ( isspace( (BYTE)sIn[ix] ) ) //貌似把空格编码成%20或者+都可以
            //{
            //    buf[0] = '+';
            //}
            else
            {
                buf[0] = '%';
                buf[1] = toHex( (BYTE)sIn[ix] >> 4 );
                buf[2] = toHex( (BYTE)sIn[ix] % 16);
            }
            sOut += (char *)buf;
        }
        return sOut;
    };
    
    static std::string URLDecode(const std::string &sIn)
    {
        std::string sOut;
        for( size_t ix = 0; ix < sIn.size(); ix++ )
        {
            BYTE ch = 0;
            if(sIn[ix]=='%')
            {
                ch = (fromHex(sIn[ix+1])<<4);
                ch |= fromHex(sIn[ix+2]);
                ix += 2;
            }
            else if(sIn[ix] == '+')
            {
                ch = ' ';
            }
            else
            {
                ch = sIn[ix];
            }
            sOut += (char)ch;
        }
        return sOut;
    }
    
    //重定向输出
    static bool logFile(std::string logPath){
        
        int fd = open(logPath.c_str(), O_WRONLY|O_APPEND|O_CREAT,0666);
        if (fd < 0) {
            
            perror("open error");
            
            return false;
        }else{
            
            
            if (dup2(fd, STDOUT_FILENO) < 0 || dup2(fd, STDERR_FILENO) < 0) {
              
                perror("dup2 error");
                return false;
            }
        }
        
        return true;
    }

};

#endif /* Utils_hpp */
